﻿namespace CqCore.Commands
{
    public abstract class CommandResultBase
    {
        protected object SuccessData { get; }
        public string FailureReason { get; }
        public bool IsSuccess => string.IsNullOrEmpty(FailureReason);

        protected CommandResultBase() { }

        protected CommandResultBase(string failureReason, object successData)
        {
            this.FailureReason = failureReason;
            this.SuccessData = successData;
        }
    }

    public class CommandResult<T> : CommandResultBase
    {
        public CommandResult()
            : base()
        { }

        public CommandResult(string failureReason, T successData)
            : base(failureReason, successData)
        { }

        public T GetData()
        {
            return (T)this.SuccessData;
        }

        public static CommandResult<T> Success(T data)
        {
            return new CommandResult<T>(null, data);
        }

        public static CommandResult<T> Failure(string reason)
        {
            return new CommandResult<T>(reason, default(T));
        }
    }

    public class CommandObjectResult : CommandResult<object>
    {
        public CommandObjectResult(string failureReason, object successData)
            : base(failureReason, successData)
        { }

        public static CommandObjectResult Success(object data)
        {
            return new CommandObjectResult(null, data);
        }

        public static CommandObjectResult Failure(string reason)
        {
            return new CommandObjectResult(reason, default(object));
        }
    }
}
